package com.hujing.springsource.a39;

import org.springframework.boot.SpringApplication;
import org.springframework.boot.WebApplicationType;
import org.springframework.boot.web.embedded.tomcat.TomcatServletWebServerFactory;
import org.springframework.boot.web.servlet.server.ServletWebServerFactory;
import org.springframework.context.ApplicationContextInitializer;
import org.springframework.context.ApplicationEvent;
import org.springframework.context.ApplicationListener;
import org.springframework.context.ConfigurableApplicationContext;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

import java.lang.reflect.Method;

/**
 * springboot执行流程-构造
 */
@Configuration
public class A39_1 {

    public static void main(String[] args) throws Exception {
        System.out.println("1.演示获取Bean Definition 源");
        SpringApplication springApplication = new SpringApplication(A39_1.class);
        System.out.println("2.演示推断应用类型");
        Method deduceFromClasspath = WebApplicationType.class.getDeclaredMethod("deduceFromClasspath");
        deduceFromClasspath.setAccessible(true);
        //反射调用方法
        System.out.println("\t 应用类型："+deduceFromClasspath.invoke(null));
        System.out.println("3.演示ApplicationContext初始化器");
        //添加初始化器
        springApplication.addInitializers(applicationContext -> System.out.println("ApplicationContext初始化器"));
        System.out.println("4.演示监听器与事件");
        //添加监听器
        springApplication.addListeners(event -> System.out.println("监听器：" + event.getClass().getName()));
        System.out.println("5.演示主类推断");
        Method deduceMainApplicationClass = SpringApplication.class.getDeclaredMethod("deduceMainApplicationClass");
        deduceMainApplicationClass.setAccessible(true);
        //反射调用方法
        System.out.println("\t 主类：" + deduceMainApplicationClass.invoke(springApplication));

        ConfigurableApplicationContext context = springApplication.run(args);
        String[] names = context.getBeanDefinitionNames();
        for (String name : names) {
            System.out.println("name:" + name + " 来源：" + context.getBeanFactory().getBeanDefinition(name).getResourceDescription());
        }

        context.close();

    }

    static class Bean1 {
    }

    static class Bean2 {
    }

    static class Bean3 {
    }

    @Bean
    public ServletWebServerFactory servletWebServerFactory() {
        return new TomcatServletWebServerFactory();
    }

}
